package com.ctshk.rpc.scenic.service.impl;


import com.alibaba.fastjson.JSON;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.core.toolkit.CollectionUtils;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.ctshk.common.enums.IsDeletedCode;
import com.ctshk.common.enums.SystemError;
import com.ctshk.common.exception.BusinessException;
import com.ctshk.common.model.PageResponse;
import com.ctshk.common.model.TokenUser;
import com.ctshk.common.utils.DateUtil;
import com.ctshk.common.utils.EntityUtil;
import com.ctshk.rpc.cms.req.BannerPositionByTypeReq;
import com.ctshk.rpc.cms.service.INoticeService;
import com.ctshk.rpc.order.scenic.service.IScenicOrderService;
import com.ctshk.rpc.scenic.dto.*;
import com.ctshk.rpc.scenic.entity.*;
import com.ctshk.rpc.scenic.mapper.*;
import com.ctshk.rpc.scenic.req.ScenicReservationListReq;
import com.ctshk.rpc.scenic.req.ScenicReservationOrderReq;
import com.ctshk.rpc.scenic.service.IScenicReservationService;
import com.ctshk.rpc.system.dto.MainDataCurrencyListDTO;
import com.ctshk.rpc.system.dto.ScenicDTO;
import com.ctshk.rpc.system.dto.SysDepartmentDTO;
import com.ctshk.rpc.system.dto.UserDTO;
import com.ctshk.rpc.system.req.MainDataCurrencyListReq;
import com.ctshk.rpc.system.service.*;
import com.github.houbb.heaven.util.util.CollectionUtil;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.lang3.StringUtils;
import org.apache.dubbo.config.annotation.DubboReference;
import org.apache.dubbo.config.annotation.DubboService;
import org.springframework.beans.factory.annotation.Autowired;

import java.math.BigDecimal;
import java.time.LocalDate;
import java.time.LocalDateTime;
import java.time.format.DateTimeFormatter;
import java.util.*;
import java.util.stream.Collectors;

/**
 * <p>
 * 预定中心门票 服务实现类
 * </p>
 *
 * @author 张志朋
 * @since 2021-02-22
 */
@DubboService
@Slf4j
public class ScenicReservationServiceImpl extends ServiceImpl<ScenicProductMapper, ScenicProduct> implements IScenicReservationService {

    @Autowired
    ScenicProductSaleStrategyMapper scenicProductSaleStrategyMapper;
    @Autowired
    private ScenicProductMapper scenicProductMapper;
    @Autowired
    private ScenicProductServiceImpl productService;
    @Autowired
    private ScenicProductCostStrategySpecAttrMapper scenicProductCostStrategySpecAttrMapper;

    @DubboReference
    private ISceneService iSceneService;
    @DubboReference
    private IScenicOrderService orderService;
    @Autowired
    ScenicProductChannelOfflineAgentCustomMapper scenicProductChannelOfflineAgentCustomMapper;

    @DubboReference
    private IMainDataTicketScenicService iMainDataTicketScenicService;
    @Autowired
    ScenicProductChannelOnlineThirdPlatformMapper scenicProductChannelOnlineThirdPlatformMapper;

    @Autowired
    ScenicProductChannelOnlineSelfPlatformMapper scenicProductChannelOnlineSelfPlatformMapper;
    @Autowired
    private ScenicProductCostStrategySpecStockMapper scenicProductCostStrategySpecStockMapper;
    @Autowired
    private ScenicProductSaleStrategyVaildDateMapper scenicProductSaleStrategyVaildDateMapper;
    @Autowired
    private ScenicProductChannelOfflineMapper scenicProductChannelOfflineMapper;
    @Autowired
    private ScenicProductChannelOfflineSelfCustomMapper scenicProductChannelOfflineSelfCustomMapper;
    @Autowired
    private ISysUserService iSysUserService;
    @Autowired
    ScenicProductTicketMapper scenicProductTicketMapper;
    @Autowired
    ScenicProductCostStrategyMapper scenicProductCostStrategyMapper;
    @Autowired
    ScenicProductCostStrategyVaildDateMapper scenicProductCostStrategyVaildDateMapper;
    @DubboReference
    private ISysDepartmentService sysDepartmentService;

    @DubboReference
    private IMainDataCurrencyService iMainDataCurrencyService;

    @DubboReference
    private INoticeService iNoticeService;

    /**
     * 查询预定中心景点门票列表
     *
     * @param reservationListReq 入参
     * @return 返回值
     */
    @Override
    public PageResponse<ScenicReservationListDTO> queryList(ScenicReservationListReq reservationListReq,TokenUser tokenUser) {
        String date = DateUtil.fmt(LocalDateTime.now());
        reservationListReq.setDate(date);
        IPage<ScenicReservationListDTO> page = new Page<>(reservationListReq.getPageNo(), reservationListReq.getPageSize());
        UserDTO userDTO = iSysUserService.queryCacheUser(tokenUser.getId());
        page = scenicProductMapper.queryByList(reservationListReq, page,tokenUser.getId(),userDTO.getDeptId());
        if(page.getRecords().size() == 0){
            //查询结果为空
            return null;
        }
        List<ScenicReservationListDTO> listDTOS= getList(page.getRecords(),userDTO);
        if(CollectionUtil.isEmpty(page.getRecords())){
            return null;
        }
       if(Objects.isNull(reservationListReq.getPriceSort())||reservationListReq.getPriceSort().equals("1")){
           listDTOS=listDTOS.stream().sorted(Comparator.comparing(ScenicReservationListDTO::getCostPrice).reversed()).collect(Collectors.toList());
       }else{
           listDTOS=listDTOS.stream().sorted(Comparator.comparing(ScenicReservationListDTO::getCostPrice)).collect(Collectors.toList());
       }
        PageResponse<ScenicReservationListDTO> result = new PageResponse<>(listDTOS, page.getCurrent() == 1,
                page.getTotal() <= (page.getCurrent() * page.getSize()),
                page.getTotal(), page.getCurrent(), page.getSize());
        return result;
    }

    /**
     * 根据产品id查询预定中心门票详情
     *
     * @param id 产品id
     * @return
     */
    @Override
    public ScenicTicketDetailsDTO query(Long id,TokenUser tokenUser) {

        ScenicProduct scenicProduct = scenicProductMapper.selectById(id);
        //查询线下渠道策略
        String time = DateUtil.fmt(LocalDateTime.now());
        //加幅类型(1 数值，2百分比)
        Integer adjustType = 0;
        BigDecimal amount = new BigDecimal("0");
        Double percent = 0.0;
        int moreTicket=99999999;
        Integer isLimit=0;
        Map<String,Long> name1=new HashMap<>();
        //先拿到成本价  查询当前的增幅策略  计算价格返回
        QueryWrapper<ScenicProductCostStrategySpecStock> wrapper = new QueryWrapper<>();
        wrapper.eq("product_id",id);
        //先查询当前生效的成本策略 然后查询到当前所有的成本价
        ScenicProductCostStrategyVaildDate strategyVaildDate = scenicProductCostStrategyVaildDateMapper.queryDetail(time,id);
        QueryWrapper<ScenicProductCostStrategySpecAttr> queryWrapper = new QueryWrapper<>();
        queryWrapper.eq("product_id",id);
        queryWrapper.eq("strategy_id",strategyVaildDate.getStrategyId());
        queryWrapper.eq("is_deleted",0);
        List<ScenicProductCostStrategySpecAttr> specAttrs = scenicProductCostStrategySpecAttrMapper.selectList(queryWrapper);
        for(ScenicProductCostStrategySpecAttr e:specAttrs){
            name1.put(e.getAttributeName(),e.getSpecId());
        }
        wrapper = new QueryWrapper<>();
        wrapper.eq("product_id",id);
        wrapper.eq("strategy_id",strategyVaildDate.getStrategyId());
        wrapper.eq("is_deleted",0);
        List<ScenicProductCostStrategySpecStock> stocks = scenicProductCostStrategySpecStockMapper.selectList(wrapper);
        //查询加幅策略
        ScenicProductSaleStrategyVaildDate saleStrategyVaildDate = scenicProductSaleStrategyVaildDateMapper.queryDetail(time,id);
       if(saleStrategyVaildDate != null){
            QueryWrapper<ScenicProductChannelOffline> queryWrapperOfline = new QueryWrapper<>();
            queryWrapperOfline.eq("product_id",id);
            queryWrapperOfline.eq("is_deleted",0);
            queryWrapperOfline.eq("strategy_id",saleStrategyVaildDate.getStrategyId());
            // 线下渠道类型（1：自营渠道 2：代理商）
            queryWrapperOfline.eq("channel_type",1);
            //查询上线的权限
           ScenicProductChannelOffline scenicProductChannelOffline =  scenicProductChannelOfflineMapper.selectOne(queryWrapperOfline);
           //获取增幅
           if(!Objects.isNull(scenicProductChannelOffline)){
                    //门票线下代理商自定义权限
                    QueryWrapper<ScenicProductChannelOfflineSelfCustom> customQueryWrapper = new QueryWrapper<>();
                    customQueryWrapper.eq("product_id", scenicProductChannelOffline.getProductId());
                    customQueryWrapper.eq("offline_id", scenicProductChannelOffline.getId());
                    List<ScenicProductChannelOfflineSelfCustom> selfCustoms = scenicProductChannelOfflineSelfCustomMapper.selectList(customQueryWrapper);
                    if(CollectionUtils.isNotEmpty(selfCustoms)){
                        ScenicProductChannelOfflineSelfCustom selfCustom = selfCustoms.get(0);
                        //权限范围类型（1：自营禁售 2 所有部门 3指定部门/人员）',
                        switch (scenicProductChannelOffline.getVisableType()){
                            case 1:
                                //禁售
                                return null;
                            case 2:
                                adjustType = selfCustom.getAdjustType();
                                amount = selfCustom.getAmount() == null ? amount : selfCustom.getAmount();
                                percent = selfCustom.getPercent() == null ? percent : selfCustom.getPercent();
                                break;
                            case 3:
                                Map<Long,ScenicProductChannelOfflineSelfCustom> customMap=new HashMap<>();
                                for(ScenicProductChannelOfflineSelfCustom e:selfCustoms){
                                    customMap.put(e.getRelationId(),e);
                                }
                                if(!Objects.isNull(customMap.get(tokenUser.getId()))){
                                    adjustType = customMap.get(tokenUser.getId()).getAdjustType();
                                    amount = customMap.get(tokenUser.getId()).getAmount();
                                    percent = customMap.get(tokenUser.getId()).getPercent();
                                }else {
                                    SysDepartmentDTO dto = sysDepartmentService.queryByUserId(tokenUser.getId());
                                    if((!Objects.isNull(dto))&&(!Objects.isNull(customMap.get(dto.getId())))){
                                        adjustType = customMap.get(dto.getId()).getAdjustType();
                                        amount = customMap.get(dto.getId()).getAmount();
                                        percent = customMap.get(dto.getId()).getPercent();
                                    }else{
                                        return null;
                                    }
                                }
                                break;
                        }
                        //
                        isLimit=selfCustom.getIsLimit()==null?0:selfCustom.getIsLimit();
                        if(isLimit==1){
                             moreTicket=selfCustom.getLimitNum()==null?0:selfCustom.getLimitNum();
                        }
                    }
            }
        }else{
           return null;
       }
       if(adjustType==0){
           //没有查询到当前用户的增幅  没设置或者没权限
           return null;
       }
        ScenicTicketDetailsDTO ticketDetailsDTO = EntityUtil.copy(scenicProduct, ScenicTicketDetailsDTO.class);
        List<SpecAttribute> specList = new ArrayList<>();
        for(ScenicProductCostStrategySpecStock e:stocks){
            QueryWrapper<ScenicProductCostStrategy> customQueryWrapper = new QueryWrapper<>();
            customQueryWrapper.eq("id", e.getStrategyId());
            ScenicProductCostStrategy selfCustoms = scenicProductCostStrategyMapper.selectOne(customQueryWrapper);
            SpecAttribute attribute=new SpecAttribute();
            attribute.setSpecName1(e.getAttr1Name());
            attribute.setSpecName2(e.getAttr2Name());
            attribute.setSpecId1(name1.get(e.getAttr1Name()));
            attribute.setSpecId2(name1.get(e.getAttr2Name()));
            BigDecimal costPrice = e.getCostPrice() == null ? new BigDecimal("0") : e.getCostPrice();
            costPrice=costPrice.multiply(new BigDecimal(selfCustoms.getExchangeRate()));
            //服务费
            BigDecimal reserveCharge = new BigDecimal("0.0");
            //加幅价格
            BigDecimal adjusAmount = new BigDecimal("0.0");
            if(scenicProduct.getReserveChargeType() == 1){
                reserveCharge = scenicProduct.getReserveCharge();
            }else if(scenicProduct.getReserveChargeType() == 2){
                reserveCharge = scenicProduct.getReserveCharge().multiply(costPrice).divide(new BigDecimal("100"));
            }
            if(adjustType == 1){
                adjusAmount = amount;
            }else if(adjustType == 2){
                adjusAmount = costPrice.multiply(new BigDecimal(percent)).divide(new BigDecimal("100"));
            }
            attribute.setMoney(costPrice.add(reserveCharge).add(adjusAmount).setScale(2,BigDecimal.ROUND_UP));
            attribute.setAmount(costPrice.add(adjusAmount).setScale(2,BigDecimal.ROUND_UP));
            int surplusStock = e.getSurplusStock();
            if(moreTicket<=surplusStock){
                if(isLimit==1){
                 Integer salaNumber= Optional.ofNullable(
                         orderService.querySalaNumber(1,e.getProductId(),tokenUser.getId()).getData())
                         .orElse(0);
                 Integer moreTicket1=moreTicket-salaNumber;
                 attribute.setMoreTicket(moreTicket1);
                }
            }else{
                attribute.setMoreTicket(surplusStock);
            }
            QueryWrapper<ScenicProductTicket>  ticketQueryWrapper = new QueryWrapper();
            ticketQueryWrapper.eq("stock_id",e.getId());
            ticketQueryWrapper.eq("attr1_name",e.getAttr1Name());
            ticketQueryWrapper.eq("attr2_name",e.getAttr2Name());
            ticketQueryWrapper.eq("product_id",e.getProductId());
            List<ScenicProductTicket> scenicProductTickets = scenicProductTicketMapper.selectList(ticketQueryWrapper);
            if(CollectionUtils.isNotEmpty(scenicProductTickets)){
                ScenicProductTicket scenicProductTicket = scenicProductTickets.get(0);
                attribute.setTicketId(scenicProductTicket.getId());
            }
            attribute.setStockId(e.getId());
            attribute.setStrategyId(e.getStrategyId());
            specList.add(attribute);
        }
        ScenicDTO scenicDTO =iSceneService.quertByiId(scenicProduct.getScenicId().toString());
        ticketDetailsDTO.setScenicLevel(scenicDTO.getScenicLevel());
        ticketDetailsDTO.setScenicName(scenicDTO.getScenicLocation());
        ticketDetailsDTO.setSpecList(specList);
        //查询代理商
        QueryWrapper<ScenicProductChannelOffline> offlineQueryWrapper = new QueryWrapper<>();
        offlineQueryWrapper.eq("product_id", strategyVaildDate.getProductId());
        offlineQueryWrapper.eq("is_deleted", 0);
        offlineQueryWrapper.eq("strategy_id", saleStrategyVaildDate.getStrategyId());
        // 线下渠道类型（1：自营渠道 2：代理商）
        offlineQueryWrapper.eq("channel_type", 2);
        List<ScenicProductChannelOffline> channelOfflineList = scenicProductChannelOfflineMapper.selectList(offlineQueryWrapper);
        if (CollectionUtils.isNotEmpty(channelOfflineList)) {
            ScenicProductChannelOffline scenicProductChannelOffline = channelOfflineList.get(0);
            if (scenicProductChannelOffline.getVisableType() != null) {
                if (scenicProductChannelOffline.getVisableType().intValue() == 2
                        || scenicProductChannelOffline.getVisableType().intValue() == 3) {
                    ticketDetailsDTO.setUsed(true);
                } else {
                    ticketDetailsDTO.setUsed(false);
                }
            }
        }
        return ticketDetailsDTO;
    }

    /**
     * 默认推荐15个
     *
     * @return
     */
    @Override
    public List<ScenicReservationListDTO> recommendedList(TokenUser tokenUser){
        //todo 上线去掉
        UserDTO userDTO = iSysUserService.queryCacheUser(tokenUser.getId());
        String time = DateUtil.fmt(LocalDateTime.now());
        List<ScenicReservationListDTO> listDTOList = scenicProductMapper.queryByList15(time,tokenUser.getId(),userDTO.getDeptId());
        return getList(listDTOList,userDTO);
    }

    /**
     * 根据产品信息获取订单信息
     *
     * @param scenicReservationOrderReq 产品信息
     * @return 订单信息
     */
    @Override
    public ScenicReservationGetOrderDTO getOrderInfo(ScenicReservationOrderReq scenicReservationOrderReq) {
        ScenicProduct scenicProduct = scenicProductMapper.selectById(scenicReservationOrderReq.getId());
        if(null == scenicProduct){
            throw new BusinessException(SystemError.SYS_411);
        }
        ScenicReservationGetOrderDTO dto = EntityUtil.copy(scenicProduct, ScenicReservationGetOrderDTO.class);
        if(1 == scenicProduct.getVaildType()){
            Double vaildDay = scenicProduct.getVaildDay();
            dto.setVaildTime("购买后"+vaildDay+"天有效");
        } else if(2 == scenicProduct.getVaildType()){
            String vaildDayBegin =DateUtil.fmt(scenicProduct.getVaildDayBegin(),"yyyy-MM-dd");
            String vaildDayEnd = DateUtil.fmt(scenicProduct.getVaildDayEnd(),"yyyy-MM-dd");

            dto.setVaildTime(vaildDayBegin + "_" + vaildDayEnd);
        }

        BigDecimal reserveCharge = scenicProduct.getReserveCharge();

        // 1:数值  2:百分比
        if(null != scenicProduct.getReserveChargeType() && 1 == scenicProduct.getReserveChargeType()){
            dto.setServiceAomunt(scenicProduct.getReserveCharge());
        } else if(null != scenicProduct.getReserveChargeType() && 2 == scenicProduct.getReserveChargeType()){
            QueryWrapper<ScenicProductCostStrategySpecStock> queryWrapper;
            if(!(null == scenicReservationOrderReq.getSpecId1() && null == scenicReservationOrderReq.getSpecId2())){
                Long productId = scenicReservationOrderReq.getId();
                String specName1 = scenicReservationOrderReq.getSpecName1();
                String specName2 = scenicReservationOrderReq.getSpecName2();
                queryWrapper = new QueryWrapper<>();
                queryWrapper.lambda().eq(ScenicProductCostStrategySpecStock::getProductId,productId);
                queryWrapper.lambda().eq(ScenicProductCostStrategySpecStock::getAttr1Name,specName1);
                queryWrapper.lambda().eq(ScenicProductCostStrategySpecStock::getAttr2Name,specName2);
                List<ScenicProductCostStrategySpecStock> specStocks = scenicProductCostStrategySpecStockMapper.selectList(queryWrapper);
                // 根据产品id 规格1属性id 规格2属性id 查出唯一的值
                if(CollectionUtils.isNotEmpty(specStocks)){
                    ScenicProductCostStrategySpecStock specStock = specStocks.get(0);
                    ScenicProductCostStrategy strategy = scenicProductCostStrategyMapper.selectById(specStock.getStrategyId());
                    BigDecimal costPrice = specStock.getCostPrice().multiply(new BigDecimal(strategy.getExchangeRate()));
                    BigDecimal multiply = reserveCharge.multiply(costPrice).divide(new BigDecimal("100"));
                    dto.setServiceAomunt(multiply);
                }
            } else if(!(StringUtils.isBlank(scenicReservationOrderReq.getSpecName1()) && StringUtils.isBlank(scenicReservationOrderReq.getSpecName2()))){
                Long productId = scenicReservationOrderReq.getId();
                String specName1 = scenicReservationOrderReq.getSpecName1();
                String specName2 = scenicReservationOrderReq.getSpecName2();
                queryWrapper = new QueryWrapper<>();
                queryWrapper.lambda().eq(ScenicProductCostStrategySpecStock::getProductId,productId);
                queryWrapper.lambda().eq(ScenicProductCostStrategySpecStock::getAttr1Name,specName1);
                queryWrapper.lambda().eq(ScenicProductCostStrategySpecStock::getAttr2Name,specName2);
                List<ScenicProductCostStrategySpecStock> specStocks = scenicProductCostStrategySpecStockMapper.selectList(queryWrapper);
                if(CollectionUtils.isNotEmpty(specStocks)){
                    ScenicProductCostStrategySpecStock specStock = specStocks.get(0);
                    ScenicProductCostStrategy strategy = scenicProductCostStrategyMapper.selectById(specStock.getStrategyId());
                    BigDecimal costPrice = specStock.getCostPrice().multiply(new BigDecimal(strategy.getExchangeRate()));
                    BigDecimal multiply = reserveCharge.multiply(costPrice).divide(new BigDecimal("100"));
                    QueryWrapper<ScenicProductTicket> ticketQueryWrapper = new QueryWrapper<>();
                    ticketQueryWrapper.eq("stock_id",specStock.getId());
                    ticketQueryWrapper.eq("is_deleted",0);
                    List<ScenicProductTicket> ticketList = scenicProductTicketMapper.selectList(ticketQueryWrapper);
                    if(CollectionUtils.isNotEmpty(ticketList)){
                        ScenicProductTicket scenicProductTicket = ticketList.get(0);
                        dto.setTicketId(scenicProductTicket.getId());
                    }
                    dto.setServiceAomunt(multiply);
                }
            }
        }
        dto.setServiceAomunt(dto.getServiceAomunt().setScale(2,BigDecimal.ROUND_UP));
        return dto;
    }

    /**
     * 根据币种名称获取汇率
     *
     * @param currencySy
     * @return
     */
    private BigDecimal getCrmExchangeRateByName(String currencySy) {
        MainDataCurrencyListReq mainDataCurrencyListReq = new MainDataCurrencyListReq();
        mainDataCurrencyListReq.setName(currencySy);
        PageResponse<MainDataCurrencyListDTO> list = iMainDataCurrencyService.list(mainDataCurrencyListReq);
        if (com.baomidou.mybatisplus.core.toolkit.CollectionUtils.isEmpty(list.getRecords())) {
            throw new BusinessException(SystemError.AIREXPRESS_ORDER_60003);
        }
        return list.getRecords().get(0).getCrmExchangeRate();
    }
    private List<ScenicReservationListDTO>  getList(List<ScenicReservationListDTO> records,UserDTO userDTO){
        log.info("【景点门票服务-查询景点门票的产品列表】获取列表入参, data{}", JSON.toJSONString(records));
        //傳入當前用户可以查询的产品
        String date = DateUtil.fmt(LocalDateTime.now());
        List<Long> productids = records.stream().map(ScenicReservationListDTO::getId).collect(Collectors.toList());
        Map<Long, ScenicChargeDTO> cbmap = new HashMap<>();
        //查询所有产品的汇率
        //if (null != productids || !Objects.isNull(productids)){
        if (CollectionUtil.isNotEmpty(productids)) {
            List<ScenicChargeDTO> scenicChargeDTOS = scenicProductCostStrategyVaildDateMapper.queryCostByProductIds(date,StringUtils.join(productids, ","));
            for(ScenicChargeDTO e:scenicChargeDTOS){
                cbmap.put(e.getProductid(),e);
            }
        }
        //查询所有产品的增幅  offlineId  作为map key
        List<Long> offlineIds=records.stream().map(ScenicReservationListDTO::getOfflineId).collect(Collectors.toList());
        List<ScenicProductChannelOfflineSelfCustom> selfCustomss = new ArrayList<>();
        if (CollectionUtil.isNotEmpty(offlineIds)) {
            selfCustomss =
                    scenicProductChannelOfflineSelfCustomMapper.queryByOfflineIds(StringUtils.join(offlineIds, ","),
                            userDTO.getId(),userDTO.getDeptId());
        }
        Map<Long, ScenicProductChannelOfflineSelfCustom> zfmap = new HashMap<>();
        for(ScenicProductChannelOfflineSelfCustom e:selfCustomss){
            zfmap.put(e.getOfflineId(),e);
        }
        log.info("【景点门票服务-查询景点门票的产品列表】查询产品的汇率和增幅数据, rateMap:{}, increaseMap:{}", JSON.toJSONString(cbmap), JSON.toJSONString(zfmap));
        for(ScenicReservationListDTO e:records){
            ScenicChargeDTO chargeDTO=cbmap.get(e.getId());
            if(chargeDTO==null){
                continue;
            }
            e.setCurrency(chargeDTO.getCurrency());
            e.setExchangeRate(chargeDTO.getExchangeRate());
            ScenicProductChannelOfflineSelfCustom custom=zfmap.get(e.getOfflineId());
            BigDecimal zf=new BigDecimal(0);
            BigDecimal cb=chargeDTO.getCostPrice().multiply(new BigDecimal(chargeDTO.getExchangeRate()));
            //計算增幅
            switch (custom.getAdjustType()){
                case 1:
                    zf=custom.getAmount();
                    break;
                case 2:
                    zf=cb.multiply(new BigDecimal(custom.getPercent())).divide(new BigDecimal("100"));
                    break;
            }
            //計算服務費
            BigDecimal fwf=new BigDecimal(0);
            switch (e.getReserveChargeType()){
                case 1:
                    fwf=e.getReserveCharge();
                    break;
                case 2:
                    fwf=cb.multiply(e.getReserveCharge()).divide(new BigDecimal("100"));
                    break;
            }
            e.setCostPrice(cb.add(zf).add(fwf).setScale(2,BigDecimal.ROUND_UP));
        }
        //查詢景点名称
        List<Long> scenicIds=records.stream().map(ScenicReservationListDTO::getScenicId).collect(Collectors.toList());
        Map<Long, ScenicDTO> scenicMap =queryByids(StringUtils.join(scenicIds, ","));
        for(ScenicReservationListDTO e:records){
            e.setScenicName(scenicMap.get(e.getScenicId()).getName());
        }
        return records;
    }
    private Map<Long, ScenicDTO> queryByids(String ids){
       List<ScenicDTO> scenicDTOS= iSceneService.quertByids(ids).getData();
        Map<Long, ScenicDTO> map=new HashMap<>();
       for(ScenicDTO e:scenicDTOS){
            map.put(e.getId(),e);
       }
       return map;
    }
    /**
     * 查询返回总价
     * @param type  1.自营 2代理 3线上  4第三方
     * @param stocktId 规格Id
     * @param productid 产品ID
     * @param id 自营时传用户或者部门id  代理传代理商id  第三方传第三方平台id
     * @return
     */
    @Override
    public ScenicPriceDTO queryAllPrices(Integer type, Long stocktId, Long productid, Long id, LocalDate date)  throws Exception{
        ScenicPriceDTO priceDTO= queryCostByProductId(productid,stocktId);
        BigDecimal zengfu=new BigDecimal("0");
        Integer kucun=priceDTO.getMoreTicket();

        DateTimeFormatter dateTimeFormatter = DateTimeFormatter.ofPattern("yyyy-MM-dd");
        String format = date.format(dateTimeFormatter);

        ScenicProductSaleStrategyVaildDate saleStrategyVaildDate =
                scenicProductSaleStrategyVaildDateMapper.queryDetail(format,productid);
        if(Objects.isNull(saleStrategyVaildDate)){
            throw new BusinessException(SystemError.SCENIC_5009);
        }
        switch (type){
            case 1:
                    //查询加幅策略
                    QueryWrapper<ScenicProductChannelOffline> queryWrapperOfline = new QueryWrapper<>();
                    queryWrapperOfline.eq("product_id", productid);
                    queryWrapperOfline.eq("is_deleted", IsDeletedCode.NO.getCode());
                    queryWrapperOfline.eq("strategy_id", saleStrategyVaildDate.getStrategyId());
                    // 线下渠道类型（1：自营渠道 2：代理商）
                    queryWrapperOfline.eq("channel_type", 1);
                    //查询上线的权限
                    ScenicProductChannelOffline scenicProductChannelOffline =
                            scenicProductChannelOfflineMapper.selectOne(queryWrapperOfline);
                    QueryWrapper<ScenicProductChannelOfflineSelfCustom> customQueryWrapper = new QueryWrapper<>();
                    customQueryWrapper.eq("product_id", productid);
                    customQueryWrapper.eq("offline_id", scenicProductChannelOffline.getId());
                    customQueryWrapper.eq("is_deleted",  IsDeletedCode.NO.getCode());
                    List<ScenicProductChannelOfflineSelfCustom> selfCustoms = scenicProductChannelOfflineSelfCustomMapper.selectList(customQueryWrapper);
                    switch (scenicProductChannelOffline.getVisableType()){
                        case 1:
                            //自營禁售
                            throw new BusinessException(SystemError.SCENIC_5011);
                        case 2:
                            ScenicProductChannelOfflineSelfCustom custom=selfCustoms.get(0);
                            zengfu=calculatezf(custom.getAdjustType(),custom.getAmount(),
                                    custom.getPercent(),priceDTO.getPrice());
                            if(custom.getIsLimit()==1){
                                kucun=custom.getLimitNum()==null?0:custom.getLimitNum();
                            }
                            break;
                        case 3:
                            Map<Long,ScenicProductChannelOfflineSelfCustom> customMap=new HashMap<>();
                            for(ScenicProductChannelOfflineSelfCustom e:selfCustoms){
                                customMap.put(e.getRelationId(),e);
                            }
                            ScenicProductChannelOfflineSelfCustom custom1=customMap.get(id);
                            if(Objects.isNull(custom1)){ //先get  有的话直接计算增幅   没有的话 当做传入的id是人员 查找部门  然后再判断是否有
                                SysDepartmentDTO department = sysDepartmentService.queryByUserId(id);
                                if((Objects.isNull(department))
                                        ||(Objects.isNull(customMap.get(department.getId())))){
                                    throw new BusinessException(SystemError.SCENIC_5010); //由于没找到部门跟部门增幅  返回错误
                                }else {
                                    custom1=customMap.get(department.getId());
                                    zengfu=calculatezf(custom1.getAdjustType(),custom1.getAmount(),
                                            custom1.getPercent(),priceDTO.getPrice());
                                    if(custom1.getIsLimit()==1){
                                        kucun=custom1.getLimitNum()==null?0:custom1.getLimitNum();
                                    }
                                }
                            }else{
                                zengfu=calculatezf(custom1.getAdjustType(),custom1.getAmount(),
                                        custom1.getPercent(),priceDTO.getPrice());
                                if(custom1.getIsLimit()==1){
                                    kucun=custom1.getLimitNum()==null?0:custom1.getLimitNum();
                                }
                            }
                            break;
                    }
                break;
            case 2:
                QueryWrapper<ScenicProductChannelOffline> queryWrapper = new QueryWrapper<>();
                queryWrapper.eq("product_id", productid);
                queryWrapper.eq("is_deleted", IsDeletedCode.NO.getCode());
                queryWrapper.eq("strategy_id", saleStrategyVaildDate.getStrategyId());
                // 线下渠道类型（1：自营渠道 2：代理商）
                queryWrapper.eq("channel_type", 2);
                //查询上线的权限
                ScenicProductChannelOffline dlOffline =
                        scenicProductChannelOfflineMapper.selectOne(queryWrapper);
                QueryWrapper<ScenicProductChannelOfflineAgentCustom> agentCustomQueryWrapper = new QueryWrapper<>();
                agentCustomQueryWrapper.eq("product_id", productid);
                agentCustomQueryWrapper.eq("offline_id", dlOffline.getId());
                agentCustomQueryWrapper.eq("is_deleted",  IsDeletedCode.NO.getCode());
                List<ScenicProductChannelOfflineAgentCustom> agentCustoms =
                        scenicProductChannelOfflineAgentCustomMapper.selectList(agentCustomQueryWrapper);
                switch (dlOffline.getVisableType()){
                    case  1:
                        throw new BusinessException(SystemError.SCENIC_5012);
                    case 2:
                        ScenicProductChannelOfflineAgentCustom agentCustom=agentCustoms.get(0);
                        zengfu=calculatezf(agentCustom.getAdjustType(),agentCustom.getAmount(),
                                agentCustom.getPercent(),priceDTO.getPrice());
                        if(agentCustom.getIsLimit()==1){
                            kucun=agentCustom.getLimitNum()==null?0:agentCustom.getLimitNum();
                        }
                        break;
                    case 3:
                        Map<Long,ScenicProductChannelOfflineAgentCustom> map=new HashMap<>();
                        for(ScenicProductChannelOfflineAgentCustom e:agentCustoms){
                            map.put(e.getCreateId(),e);
                        }
                        agentCustom=map.get(id);
                        if(Objects.isNull(agentCustom)){
                            zengfu=calculatezf(agentCustom.getAdjustType(),agentCustom.getAmount(),
                                    agentCustom.getPercent(),priceDTO.getPrice());
                        }
                        if(agentCustom.getIsLimit()==1){
                            kucun=agentCustom.getLimitNum()==null?0:agentCustom.getLimitNum();
                        }
                        break;
                }
                break;
            case 3:
                //线上自营ScenicProductChannelOnlineSelfPlatform
                QueryWrapper<ScenicProductChannelOnlineSelfPlatform> selfPlatformQueryWrapper = new QueryWrapper<>();
                selfPlatformQueryWrapper.eq("product_id", productid);
                selfPlatformQueryWrapper.eq("is_deleted", IsDeletedCode.NO.getCode());
                selfPlatformQueryWrapper.eq("strategy_id", saleStrategyVaildDate.getStrategyId());
                ScenicProductChannelOnlineSelfPlatform selfPlatformQueryWrapperVo = new ScenicProductChannelOnlineSelfPlatform();

                log.info(String.format("调用景点门票服务获取总价查询参数,channelType:%s,productId:%s ,departDate:%s ,id:%s  ", type, productid, date, id));

                if (id != null){
                    selfPlatformQueryWrapper.eq("channel_id", id);
                    //门票线上自营
                    selfPlatformQueryWrapperVo = scenicProductChannelOnlineSelfPlatformMapper.selectOne(selfPlatformQueryWrapper);
                }
                if(Objects.isNull(selfPlatformQueryWrapperVo)){
                    //當前參評沒有現象自營
                    throw new BusinessException(SystemError.SCENIC_5020);
                }else{
                    log.info(String.format("调用景点门票服务获取总价查询返回数据,adjustType:%s,amount:%s ,percent:%s ,price:%s  ", selfPlatformQueryWrapperVo.getAdjustType(), selfPlatformQueryWrapperVo.getAmount(), selfPlatformQueryWrapperVo.getPercent(), priceDTO.getPrice()));
                    zengfu=calculatezf(selfPlatformQueryWrapperVo.getAdjustType(),selfPlatformQueryWrapperVo.getAmount(),
                            selfPlatformQueryWrapperVo.getPercent(),priceDTO.getPrice());
                    log.info(String.format("调用景点门票服务获取总价,zengfu:%s", zengfu));
                    if(null != selfPlatformQueryWrapperVo.getIsLimit() && selfPlatformQueryWrapperVo.getIsLimit()==1){
                        kucun=selfPlatformQueryWrapperVo.getLimitNum()==null?0:selfPlatformQueryWrapperVo.getLimitNum();
                    }
                }

                break;
            case 4:
                QueryWrapper<ScenicProductChannelOnlineThirdPlatform> thirdPlatformReqQueryWrapper = new QueryWrapper<>();
                thirdPlatformReqQueryWrapper.eq("product_id", productid);
                thirdPlatformReqQueryWrapper.eq("is_deleted", IsDeletedCode.NO.getCode());
                thirdPlatformReqQueryWrapper.eq("strategy_id", saleStrategyVaildDate.getStrategyId());
                thirdPlatformReqQueryWrapper.eq("platform_id", id);
                ScenicProductChannelOnlineThirdPlatform thirdPlatformReq=
                        scenicProductChannelOnlineThirdPlatformMapper.selectOne(thirdPlatformReqQueryWrapper);
                if(Objects.isNull(thirdPlatformReq)){
                      throw new BusinessException(SystemError.SCENIC_5013);
                }else{
                    zengfu=calculatezf(thirdPlatformReq.getAdjustType(),thirdPlatformReq.getAmount(),
                            thirdPlatformReq.getPercent(),priceDTO.getPrice());
                    if(thirdPlatformReq.getIsLimit()==1){
                        kucun=thirdPlatformReq.getLimitNum()==null?0:thirdPlatformReq.getLimitNum();
                    }
                }
                break;
        }
        priceDTO.setMoreTicket(kucun);
        priceDTO.setMoney(zengfu.add(priceDTO.getPrice()).add(priceDTO.getReserveCharge()));
        log.info(String.format("queryAllPrices接口返回信息日志：,priceDTO:%s", priceDTO));
        return priceDTO;
    }

    /**
     * 计算增幅内部方法
     * @param adjustType 增幅类型
     * @param amount 增幅数值
     * @param percent 增幅百分比
     * @param price 价格 (不带服务费)
     * @return
     */
    private  BigDecimal calculatezf(Integer adjustType,BigDecimal amount,Double percent,BigDecimal price){
        BigDecimal zf=new BigDecimal("0");
        switch (adjustType){
            case 1:
                zf=amount;
                break;
            case 2:
                zf= price.multiply(new BigDecimal(percent)).divide(new BigDecimal("100"));
                break;
        }
        return  zf;
    }

    @Override
    public  ScenicPriceDTO queryCostByProductId(Long productId,Long stockId) {
        ScenicPriceDTO scenicPriceDTO=new ScenicPriceDTO();
        //门票成本价格加幅有效期
        ScenicProductCostStrategyVaildDate strategyVaildDate =
                scenicProductCostStrategyVaildDateMapper.queryDetail(DateUtil.fmt(LocalDateTime.now()),productId);
        if(Objects.isNull(strategyVaildDate)){
            throw new BusinessException(SystemError.SCENIC_5008);
        }
        //门票成本策略
        QueryWrapper<ScenicProductCostStrategy> customQueryWrapper = new QueryWrapper<>();
        customQueryWrapper.eq("id", strategyVaildDate.getStrategyId());
        ScenicProductCostStrategy selfCustoms = scenicProductCostStrategyMapper.selectOne(customQueryWrapper);
        //门票库存
        ScenicProductCostStrategySpecStock stocks;
        if(Objects.isNull(stockId)){
            stocks = scenicProductCostStrategySpecStockMapper.queryByStrategyId(selfCustoms.getId());
        }else{
            stocks = scenicProductCostStrategySpecStockMapper.queryById(stockId);
        }
        BigDecimal costPrice=stocks.getCostPrice()==null?BigDecimal.valueOf(0):stocks.getCostPrice();
        scenicPriceDTO.setPrice(costPrice.multiply(BigDecimal.valueOf(selfCustoms.getExchangeRate())));
        scenicPriceDTO.setMoreTicket(stocks.getSurplusStock());
        //景点门票产品
        QueryWrapper<ScenicProduct> productWrapper = new QueryWrapper<>();
        productWrapper.eq("id",productId);
        ScenicProduct scenicProduct= scenicProductMapper.selectOne(productWrapper);
        switch (scenicProduct.getReserveChargeType()){
            case 1:
                scenicPriceDTO.setReserveCharge(scenicProduct.getReserveCharge());
                break;
            case 2:
                scenicProduct.setReserveCharge(scenicProduct.getReserveCharge().multiply(scenicPriceDTO.getPrice()).divide(new BigDecimal("100")));
                break;
        }
        return scenicPriceDTO;
    }

    /**
     * 查询首页通告
     * @param
     * @return
     */
    @Override
    public List<NoticeDTO> queryListByCode() {
        BannerPositionByTypeReq req = new BannerPositionByTypeReq();
        req.setCode("TICKET_NOTICE");
        List<NoticeDTO> noticeList = EntityUtil.copyList(iNoticeService.queryListByCode(req), NoticeDTO.class);
        return noticeList;
    }
}












